//
//  GameObject.cpp
//  RenderV1
//
//  Created by 黄翔 on 2019/10/20.
//  Copyright © 2019 黄翔. All rights reserved.
//

#include "GameObject.h"
#include "Render.h"
#include "render_v1_typedef.h"
#include "Camera.h"
class Camera;

unsigned int hxe::GameObject::genInstanceId = 0;

hxe::GameObject::GameObject(std::string name)
{
    this->name = name;
    this->instanceId = ++genInstanceId;
    this->transform = new Transform(this);
    this->components = nullptr;
    this->layer = layerDefault;
}

hxe::GameObject::~GameObject()
{
    for (int i = 0; i < transform->getChildCount(); i++)
    {
        transform->getChild(i)->gameObject->drop();
    }

    Component* c = components;
    while (c != nullptr) {
        Component* old = c;
        c = c->next;
        old->drop();
    }

    this->transform->drop();
}

void hxe::GameObject::addComponent(Component* component)
{
    component->next = components;
    components = component;
    component->gameObject = this;
}

hxe::Component* hxe::GameObject::getComponent(std::string name)
{
    Component* c = components;
    while (c != nullptr) {
        if (c->getName() == name)
        {
            return c;
        }
        c = c->next;
    }
    return nullptr;
}


void hxe::GameObject::changeLayer(int layer, bool includeChildren)
{
    this->layer = layer;

    if (includeChildren)
    {
        for (int i = 0; i < transform->getChildCount(); i++)
        {
            transform->getChild(i)->gameObject->layer = layer;;
        }
    }
}

void hxe::GameObject::update()
{
    for (int i = 0; i < transform->getChildCount(); i++)
    {
        transform->getChild(i)->gameObject->update();
    }
    Component* c = components;
    while (c != nullptr) {
        c->update();
        c = c->next;
    }
}

void hxe::GameObject::draw()
{
    if (((this->layer) & (Camera::current->cullingMask)) == 0)
    {
        return;
    }

    Component* c = components;
    while (c != nullptr) {
        if (c->getName() == "Render")
        {
            ((Render*)c)->draw();
            break;;
        }
        c = c->next;
    }

    for (int i = 0; i < transform->getChildCount(); i++)
    {
        transform->getChild(i)->gameObject->draw();
    }
}
